/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.leeassamite.ocr;

import java.awt.Color;
import java.awt.Image;
import java.awt.image.BufferedImage;
import java.awt.image.PixelGrabber;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Iterator;
import java.util.List;
import java.util.Map.Entry;
import java.util.SortedMap;

import javax.imageio.ImageIO;
/**
 *
 * @author leeass
 */
public class ImageOcr {
    public static String orc(BufferedImage buffImage)
    {
        int[][] dotArray = ImageOcr.bitmap2DotArray(buffImage);
        IWord imageProcess = new IWord(dotArray);
        IWord[] tezheng = Tezheng.getAllIWord();
        List<ComparableImpl> a_4 = ImageOcr.process2list(imageProcess, tezheng);
        return ImageOcr.Ocr2Str(a_4);
    }
    public static String orc(byte[] bytes)
    {
    	try {
	    	ByteArrayInputStream in = new ByteArrayInputStream(bytes);
	        BufferedImage buffImage;
				buffImage = ImageIO.read(in);
	    	int[][] dotArray = ImageOcr.bitmap2DotArray(buffImage);
	    	IWord imageProcess = new IWord(dotArray);
	    	IWord[] tezheng = Tezheng.getAllIWord();
	    	List<ComparableImpl> a_4 = ImageOcr.process2list(imageProcess, tezheng);
	    	return ImageOcr.Ocr2Str(a_4);
    	} catch (IOException e) {
    		// TODO Auto-generated catch block
    		e.printStackTrace();
    	}
    	return "";
    }
    
    
    private static List<ComparableImpl> process2list(IWord A_0, IWord[] A_1)
    {
        List<ComparableImpl> list = new ArrayList<ComparableImpl>();
        for (int i = 0; i < A_1.length; i++)
        {
            for (int j = 0; j <= A_0.getWidth() - 1; j++)
            {
                int num = A_0.getWidth() - (A_1[i].getWidth() / 2 + j);
                for (int k = 0; k <= A_0.d(); k++)
                {
                    int num2 = k - A_1[i].d() / 2;
                    if (num2 < 0)
                    {
                        num2 = 0;
                    }
                    int num3 = (A_1[i].d() + 1) / 2 + k;
                    if (num3 > A_0.d())
                    {
                        num3 = A_0.d();
                    }
                    int num4 = 0;
                    int num5 = 0;
                    int l;
                    for (l = num2; l < num3; l++)
                    {
                        int num6 = (A_1[i].d() / 2 - k > 0) ? (A_1[i].d() / 2 - k) : 0;
                        int num7;
                        if (num > 0)
                        {
                            num7 = A_1[i].getListC().get(num6 + l - num2) << num;
                        }
                        else
                        {
                            num7 = A_1[i].getListC().get(num6 + l - num2) >> num * -1;
                        }
                        num7 &= (int)Math.pow(2.0, (double)A_0.getWidth()) - 1;
                        num4 += ImageOcr.chuliNumber(num7);
                        if (num4 == 0)
                        {
                            num5++;
                        }
                        if (((num7 & A_0.getListC().get(l)) ^ num7) != 0)
                        {
                            break;
                        }
                    }
                    if (l == num3 && num4 != 0)
                    {
                        if (num > 0)
                        {
                            if (A_1[i].getWidth() + num < A_0.getWidth())
                            {
                                A_1[i].getWidth();
                            }
                            else
                            {
                                A_0.getWidth();
                            }
                        }
                        else
                        {
                            A_1[i].getWidth();
                        }
                        ComparableImpl item = new ComparableImpl(A_1[i].getWord(), num2 + num5, (float)num4 / (float)A_1[i].getIntF(), A_1[i].getIntF());
                        list.add(item);
                    }
                }
            }
        }
        return list;
    }
    private static int chuliNumber(int A_0)
    {
        int num = 0;
        while ((long)num < (long)(A_0))
        {
            num++;
            A_0 &= A_0 - 1;
        }
        return num;
    }
    
    private static String Ocr2Str(List<ComparableImpl> A_0)
    {
        StringBuilder stringBuilder = new StringBuilder();
        ComparableImpl comparable = new ComparableImpl();
        Collections.sort(A_0,comparable);
        SortedMap<Integer,ComparableImpl> sortedList = new java.util.TreeMap<Integer,ComparableImpl>();
        for (int i = 0; i < 4; i++)
        {
            if (A_0.size() < 4)
            {
                return "";
            }
            sortedList.put(A_0.get(i).getIntB(), A_0.get(i));
            for (int j = i + 1; j < A_0.size(); j++)
            {
                if (Math.abs(A_0.get(i).getIntB() - A_0.get(j).getIntB()) < 3)
                {
                    if (((ComparableImpl)sortedList.get(A_0.get(i).getIntB())).getIntD() < A_0.get(j).getIntD())
                    {
                        sortedList.put(A_0.get(i).getIntB(), A_0.get(j));
                    }
                    A_0.remove(j);
                    j--;
                }
            }
        }
        
        Iterator<Entry<Integer,ComparableImpl>> iterator = sortedList.entrySet().iterator();
        while (iterator.hasNext())
        {
            Entry<Integer,ComparableImpl> entry = iterator.next();
            ComparableImpl ci = entry.getValue();
            stringBuilder.append(ci.getCharA());
        }
        return stringBuilder.toString();
    }
    
//    private int[] getPixArray(Image im, int w, int h) {
//         int[] pix = new int[w * h];
//         PixelGrabber pg = null;
//         try {
//             pg = new PixelGrabber(im, 0, 0, w, h, pix, 0, w);
//             if (pg.grabPixels() != true)
//                 try {
//                     throw new java.awt.AWTException("pg error" + pg.status());
//                 } catch (Exception eq) {
//                     eq.printStackTrace();
//                 }
//         } catch (Exception ex) {
//             ex.printStackTrace();
// 
//         }
//         return pix;
//     }
    
    
    private static int getColorWeight(Color color)
    {
        ;
        return (int)color.getRed() * 19595 + (int)color.getGreen() * 38469 + (int)color.getBlue() * 7472 >> 16;
    }
    
    
        private static int[][] bitmap2DotArray(BufferedImage buffImage)
    {
        int[][] array = new int[buffImage.getHeight()][buffImage.getWidth()];
        
        for (int i = 0; i < buffImage.getHeight(); i++)
        {
            for (int j = 0; j < buffImage.getWidth(); j++)
            {

                if (170 < ImageOcr.getColorWeight(new Color(buffImage.getRGB(j, i))))
                {
                    array[i][j] = 0;
                }
                else
                {
                    array[i][j] = 1;
                }
            }
        }
        return array;
    }
//    private static char a(IWord[] A_0)
//    {
//        int num = 0;
//        int num2 = 10000;
//        for (int i = 0; i < A_0.length; i++)
//        {
//            if (num2 > A_0[i].getIntE())
//            {
//                num2 = A_0[i].getIntE();
//                num = i;
//            }
//        }
//        return A_0[num].getWord();
//    }
    
//    private static BufferedImage a(int[][] A_0)
//    {
//        BufferedImage bitmap = new Bitmap(A_0[0].length, A_0.length);
//        for (int i = 0; i < A_0.length; i++)
//        {
//            for (int j = 0; j < A_0[0].length; j++)
//            {
//                if (A_0[i][j] == 0)
//                {
//                    A_0[i][j] = 255;
//                }
//                else
//                {
//                    A_0[i][j] = 0;
//                }
//                Color color = new Color(A_0[i][j], A_0[i][j], A_0[i][j]);
//                bitmap.SetPixel(j, i, Color.();
//            }
//        }
//        return bitmap;
//    }



    
}
